/**
 * User: Justin Akin
 * Twitter: @idointernet
 * Date: 7/15/12
 */
jpackage( "twc.utils", function() {

	this.UTF8Util = {

		encode: function( string ) {

			var i, c, utftext = '';

			string = string.replace(/\r\n/g,"\n");

			for( i = 0; i < string.length; i++) {

				c = string.charCodeAt( i );

				if( c < 128 ) {
					utftext += String.fromCharCode( c );
				}
				else if( ( c > 127 ) && ( c < 2048 ) ) {
					utftext += String.fromCharCode( ( c >> 6 ) | 192 );
					utftext += String.fromCharCode( ( c & 63) | 128 );
				}
				else {
					utftext += String.fromCharCode( ( c >> 12 ) | 224 );
					utftext += String.fromCharCode( ( ( c >> 6 ) & 63 ) | 128 );
					utftext += String.fromCharCode( ( c & 63 ) | 128 );
				}

			}

			return utftext;

		},

		decode: function( utftext ) {

			var string = '';
			var i = c = c1 = c2 = 0;

			while ( i < utftext.length ) {

				c = utftext.charCodeAt( i );

				if( c < 128 ) {
					string += String.fromCharCode( c );
					i++;
				}
				else if( ( c > 191 ) && ( c < 224 ) ) {

					c2 = utftext.charCodeAt( i + 1 );
					string += String.fromCharCode( ( ( c & 31 ) << 6 ) | ( c2 & 63 ) );
					i += 2;

				}
				else {

					c2 = utftext.charCodeAt( i + 1 );
					c3 = utftext.charCodeAt( i + 2 );
					string += String.fromCharCode( ( ( c & 15 ) << 12 ) | ( ( c2 & 63 ) << 6 ) | ( c3 & 63 ) );
					i += 3;

				}

			}

			return string;

		}

	}

});
/**
 * User: Justin Akin
 * Twitter: @idointernet
 * Date: 7/14/12
 */
jpackage( "twc.utils", function() {

	var UTF8Util = this.UTF8Util;

	var keystr = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/=";

	this.Base64Util = {

		encode: function( input ) {

			var chr1, chr2, chr3, enc1, enc2, enc3, enc4, i = 0, output = "";

			input = UTF8Util.encode( input );

			while( i < input.length ) {

				chr1 = input.charCodeAt( i++ );
				chr2 = input.charCodeAt( i++ );
				chr3 = input.charCodeAt( i++ );

				enc1 = chr1 >> 2;
				enc2 = ( ( chr1 & 3 ) << 4 ) | ( chr2 >> 4 );
				enc3 = ( ( chr2 & 15 ) << 2 ) | ( chr3 >> 6 );
				enc4 = chr3 & 63;

				if( isNaN( chr2 ) ) {
					enc3 = enc4 = 64;
				}
				else if( isNaN( chr3 ) ) {
					enc4 = 64;
				}

				output = output +
					keystr.charAt( enc1 ) + keystr.charAt( enc2 ) +
					keystr.charAt( enc3 ) + keystr.charAt( enc4 );
			}

			return output;

		},

		decode: function( input ) {

			var chr1, chr2, chr3, enc1, enc2, enc3, enc4, i = 0, output = "";

			input = input.replace(/[^A-Za-z0-9\+\/\=]/g, "");

			while( i < input.length ) {

				enc1 = keystr.indexOf( input.charAt( i++ ) );
				enc2 = keystr.indexOf( input.charAt( i++ ) );
				enc3 = keystr.indexOf( input.charAt( i++ ) );
				enc4 = keystr.indexOf( input.charAt( i++ ) );

				chr1 = ( enc1 << 2 ) | ( enc2 >> 4 );
				chr2 = ( ( enc2 & 15 ) << 4 ) | ( enc3 >> 2 );
				chr3 = ( ( enc3 & 3 ) << 6 ) | enc4;

				output = output + String.fromCharCode( chr1 );

				if( enc3 != 64 ) {
					output = output + String.fromCharCode( chr2 );
				}

				if( enc4 != 64 ) {
					output = output + String.fromCharCode( chr3 );
				}

			}

			output = UTF8Util.decode( output );

			return output;

		}

	}

});

